-- 运算电路 --
--------------

-- 【相加相减相乘运算电路】

library ieee;
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_unsigned.all;

entity calculate is
    port(
        op1, op2 : in std_logic_vector(3 downto 0);
        sum, sub : out std_logic_vector(3 downto 0);
        mult     : out std_logic_vector(7 downto 0)
    );
end entity;

architecture behave of caclculate is
begin
    sum <= op1 + op2;
    sub <= op1 - op2;
    mult <= op1 * op2;
end behave;



-- 【4位串行进位加法器的设计】

library ieee;
use ieee.std_logic_1164.all;

entity adderN is
    generic(N: integer := 4)
    port(
        a, b : in std_logic_vector(N downto 1);
        cin : in std_logic;
        sum : out std_logic_vector(N downto 1);
        cout : out std_logic
    );
end adderN;

architecture behave of adderN is

    component addr
        port(
            a, b, cin : in std_logic;
            sum, cout : out std_logic
        );
    end component;

    signal carry : std_logic_vector(0 to N);

begin

    carry(0) <= cin;
    cout <= carry(N);
    gen: for i in 1 to N generate
        add: adder port map(
            a => a(i),
            b => b(i);
            cin => carry(i - 1);
            sum => sum(i);
            cout => carry(i)
        );
    end generate;

end behave;

-- component adder

library ieee;
use ieee.std_logic_1164.all;

entity adder is
    port(
        a, b, cin : in std_logic;
        sum, cout : out std_logic
    );
end adder

architecture rtl of adder is
begin
    sum <= (a xor b) xor cin;
    cout <= (a and b) or (cin and a) or (cin and b);
end rtl;



-- 【基于数据流的4位超前进位加法器】

library ieee;
use ieee.std_logic_1164.all;

entity adderN is
    generic(N: integer := 4);
    port(
        a, b : in std_logic_vector(N downto 1);
        cin : in std_logic;
        sum : out std_logic_vector(N downto 1);
        cout : out std_logic
    );
end adderN;

architecture rtl of adderN is
begin
    process(a, b, cin)
        variable vsum : std_logic_vector(N downto 1);
        variable carry : std_logic;
        begin
            carry := cin;
            for i in 1 to N loop
                vsum(i) := (a(i) xor b(i)) xor carry;
                carry := (a(i) and b(i)) or (carry and (a(i) or b(i)));
            end loop;
            sum <= vsum;
            cout <= carry;
    end process;

end rtl;

